]> git.dpolakovic.space - dpolakovic-space/commitdiff
feat: Email privacy, blob highlights and other. 1.1.0
authorDavid Polakovic
Sun, 1 Mar 2026 10:39:15 +0000 (11:39 +0100)
committerDavid Polakovic
Sun, 1 Mar 2026 10:45:08 +0000 (11:45 +0100)
- contributors email address is removed from log and shortlog
- blob syntax highlighting is fixed(?) with matlab/octave theme
- added 3em space trailing description content on front page
- added path to servers "dot.png" favicon

Git-server/Gitweb/gitweb.cgi

index 7987979041af26f0d950dc661f2c69373d4f1432..fc729be17c068b61674bff9a119b9cbea3c19c0a 100644 (file)
@@ -117,7 +117,7 @@ our $stylesheet = undef;
 # URI of GIT logo (72x27 size)
 our $logo = "static/git-logo.png";
 # URI of GIT favicon, assumed to be image/png type
-our $favicon = "static/git-favicon.png";
+our $favicon = "static/dot.png";
 # URI of gitweb.js (JavaScript code for gitweb)
 our $javascript = "static/gitweb.js";
 
@@ -202,6 +202,13 @@ our $prevent_xss = 0;
 # [Default: highlight]
 our $highlight_bin = "highlight";
 
+# Style/theme to use for syntax highlighting with highlight.
+# Set this in gitweb.conf to override the default highlight theme.
+# See available themes with: highlight --list-scripts=themes
+# Example: our $highlight_style = "moria";
+# [Default: "", use highlight's built-in default]
+our $highlight_style = "";
+
 # information about snapshot formats that gitweb is capable of serving
 our %known_snapshot_formats = (
        # name => {
@@ -577,7 +584,7 @@ our %feature = (
        'email-privacy' => {
                'sub' => sub { feature_bool('email-privacy', @_) },
                'override' => 1,
-               'default' => [0]},
+               'default' => [1]},
 );
 
 sub gitweb_get_feature {
@@ -3546,22 +3553,34 @@ sub parse_commit_text {
                } elsif ((!defined $withparents) && ($line =~ m/^parent ($oid_regex)$/)) {
                        push @parents, $1;
                } elsif ($line =~ m/^author (.*) ([0-9]+) (.*)$/) {
-                       $co{'author'} = hide_mailaddrs_if_private(to_utf8($1));
-                       $co{'author_epoch'} = $2;
-                       $co{'author_tz'} = $3;
+                       my ($author_raw, $author_epoch, $author_tz) = (to_utf8($1), $2, $3);
+                       # Extract real email before hiding, for avatar use
+                       if ($author_raw =~ m/^[^<]+<([^>]*)>/) {
+                               $co{'author_email'} = $1;
+                       }
+                       $co{'author'} = hide_mailaddrs_if_private($author_raw);
+                       $co{'author_epoch'} = $author_epoch;
+                       $co{'author_tz'} = $author_tz;
                        if ($co{'author'} =~ m/^([^<]+) <([^>]*)>/) {
                                $co{'author_name'}  = $1;
-                               $co{'author_email'} = $2;
+                               # Keep real email (already set above) for avatar; don't overwrite with redacted
+                               $co{'author_email'} ||= $2;
                        } else {
                                $co{'author_name'} = $co{'author'};
                        }
                } elsif ($line =~ m/^committer (.*) ([0-9]+) (.*)$/) {
-                       $co{'committer'} = hide_mailaddrs_if_private(to_utf8($1));
-                       $co{'committer_epoch'} = $2;
-                       $co{'committer_tz'} = $3;
+                       my ($committer_raw, $committer_epoch, $committer_tz) = (to_utf8($1), $2, $3);
+                       # Extract real email before hiding, for avatar use
+                       if ($committer_raw =~ m/^[^<]+<([^>]*)>/) {
+                               $co{'committer_email'} = $1;
+                       }
+                       $co{'committer'} = hide_mailaddrs_if_private($committer_raw);
+                       $co{'committer_epoch'} = $committer_epoch;
+                       $co{'committer_tz'} = $committer_tz;
                        if ($co{'committer'} =~ m/^([^<]+) <([^>]*)>/) {
                                $co{'committer_name'}  = $1;
-                               $co{'committer_email'} = $2;
+                               # Keep real email (already set above) for avatar; don't overwrite with redacted
+                               $co{'committer_email'} ||= $2;
                        } else {
                                $co{'committer_name'} = $co{'committer'};
                        }
@@ -4018,7 +4037,9 @@ sub run_highlighter {
                    '$_ = decode($fe, $_, FB_DEFAULT) if !utf8::decode($_);',
                    '--', "-fe=$fallback_encoding")." | ".
                  quote_command($highlight_bin).
-                 " --replace-tabs=8 --fragment $syntax_arg |"
+                 " --replace-tabs=8 --fragment --inline-css $syntax_arg" .
+                 ($highlight_style ? " --style=".quote_command($highlight_style) : "") .
+                 " |"
                or die_error(500, "Couldn't open file or run syntax highlighter");
        return $fd;
 }
@@ -4591,11 +4612,14 @@ sub git_print_authorship_rows {
        @people = ('author', 'committer') unless @people;
        foreach my $who (@people) {
                my %wd = parse_date($co->{"${who}_epoch"}, $co->{"${who}_tz"});
+               my $email_display = gitweb_check_feature('email-privacy')
+                       ? ''
+                       : ' ' . format_search_author($co->{"${who}_email"}, $who,
+                                                    esc_html("<" . $co->{"${who}_email"} . ">"));
                print "<tr><td>$who</td><td>" .
                      format_search_author($co->{"${who}_name"}, $who,
-                                          esc_html($co->{"${who}_name"})) . " " .
-                     format_search_author($co->{"${who}_email"}, $who,
-                                          esc_html("<" . $co->{"${who}_email"} . ">")) .
+                                          esc_html($co->{"${who}_name"})) .
+                     $email_display .
                      "</td><td rowspan=\"2\">" .
                      git_get_avatar($co->{"${who}_email"}, -size => 'double') .
                      "</td></tr>\n" .
@@ -5833,8 +5857,8 @@ sub git_project_list_rows {
                                        -title => $pr->{'descr_long'}},
                                        $search_regexp
                                        ? esc_html_match_hl_chopped($pr->{'descr_long'},
-                                                                   $pr->{'descr'}, $search_regexp)
-                                       : esc_html($pr->{'descr'})) .
+                                                                   $pr->{'descr'}, $search_regexp) . "&#160;&#160;&#160;"
+                                       : esc_html($pr->{'descr'}) . "&#160;&#160;&#160;") .
                      "</td>\n";
                print "<td>" . esc_html($pr->{'version'} || '-') . "</td>\n";
                print "<td>" . esc_html($pr->{'license'} || '-') . "</td>\n";
@@ -8426,14 +8450,14 @@ XML
                              "<updated>$cd{'iso-8601'}</updated>\n" .
                              "<author>\n" .
                              "  <name>" . esc_html($co{'author_name'}) . "</name>\n";
-                       if ($co{'author_email'}) {
+                       if ($co{'author_email'} && !gitweb_check_feature('email-privacy')) {
                                print "  <email>" . esc_html($co{'author_email'}) . "</email>\n";
                        }
                        print "</author>\n" .
                              # use committer for contributor
                              "<contributor>\n" .
                              "  <name>" . esc_html($co{'committer_name'}) . "</name>\n";
-                       if ($co{'committer_email'}) {
+                       if ($co{'committer_email'} && !gitweb_check_feature('email-privacy')) {
                                print "  <email>" . esc_html($co{'committer_email'}) . "</email>\n";
                        }
                        print "</contributor>\n" .
Copyright 2022-2026 David Polakovic. Individual project licenses are located in project root in full length.

Site generated using Gitweb. Read the documentation for JavaScript and cookie information. Additional source code available here under GPLv3 license.

Server for this subdomain is RFC 2324 compliant